package com.android;

import java.util.ArrayList;
import java.util.Random;

import com.android.DataBaseManager;

import android.app.Activity;
import android.app.AlertDialog;
import android.app.AlertDialog.Builder;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.graphics.LightingColorFilter;
import android.util.Log;
import android.view.View.OnClickListener;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TextView;
import android.widget.Toast;
import android.text.TextUtils;
import android.text.util.*;

public class SlideGame extends Activity{
	/** Called when the activity is first created. */
    String [][]ary = new String[4][4];
	int count,cnsl=0;
	int cnt[] = new int [16];
	EditText user;
	TextView tex,hue,herues;
	Button btn0,btn1,btn2,btn3,btn4,btn5,btn6,btn7,btn8,btn9,btn10,btn11,btn12,btn13,btn14,btn15,btnNew,btnscore,btnAstar,btntimes,btnHgtScore;
	TableLayout dataTable;
	MyCount counter = new MyCount(90000,1000);
	DataBaseManager db;
	@Override
    public void onCreate(Bundle savedInstanceState){
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        getButtonId();
        btn0.setOnClickListener(new eventClick());
        btn1.setOnClickListener(new eventClick());
        btn2.setOnClickListener(new eventClick());
        btn3.setOnClickListener(new eventClick());
        btn4.setOnClickListener(new eventClick());
        btn5.setOnClickListener(new eventClick());
        btn6.setOnClickListener(new eventClick());
        btn7.setOnClickListener(new eventClick());
        btn8.setOnClickListener(new eventClick());
        btn9.setOnClickListener(new eventClick());
        btn10.setOnClickListener(new eventClick());
        btn11.setOnClickListener(new eventClick());
        btn12.setOnClickListener(new eventClick());
        btn13.setOnClickListener(new eventClick());
        btn14.setOnClickListener(new eventClick());
        btn15.setOnClickListener(new eventClick());

        btnNew.setOnClickListener(new newGame());
        //btnGreedy.setOnClickListener(new greedyAi());
        btnAstar.setOnClickListener(new astarAi());
        
        db = new DataBaseManager(this);
        Button helpN = (Button) findViewById(R.id.Help);
        helpN.setOnClickListener(new OnClickListener() {
            public void onClick(View view) {
            	Intent explicitIntent = new Intent(SlideGame.this,GameHelp.class);
        		startActivity(explicitIntent);
            }
        });
        btnHgtScore.setOnClickListener(new OnClickListener() {
            public void onClick(View view) {
            	Intent explicitIntent = new Intent(SlideGame.this,HightScore.class);
        		startActivity(explicitIntent);
            }
        });
        buttonLock();

    }
	private class eventClick implements android.view.View.OnClickListener {
         public void onClick(View v) {//test
        	Button btnClick = (Button)findViewById(v.getId());
         	CharSequence position = findinArray(btnClick.getText());
         	String[] Fakexy = TextUtils.split(position.toString(), ",");
         	int x = Integer.valueOf(Fakexy[0]);
         	int y = Integer.valueOf(Fakexy[1]);         	
		
         	
         	if(CheckEmptyBox(x, y) == true){
         		RepaintArray();
         		count++;
         		eventGame evg =new eventGame();
         		if( evg.finalPuzzle(ary) == true ){
         			counter.cancel();
         		    buttonLock();
         		   int nu = 90 - Integer.parseInt(btntimes.getText().toString());         		
         			_showAlert("Congratulation  \n You win!\n MOVE ="+count+"\n Time ="+Integer.toString(nu)+"\n SOLVE ="+cnsl,SlideGame.this);
         			addRow();
         		}

         		btnscore.setText(Integer.toString(count));
         		
         	}
         }
	}
	private class newGame implements android.view.View.OnClickListener {
        public void onClick(View v) {
        	//Message("New Game");
        	//_showAlert("New Game",SlideGame.this);//Test message alert
        
        		initPuzzle(); RepaintArray(); buttonUnLock(); resetValue();
                counter.start();	
        	
        	
            
        }
	}
    /*private class greedyAi implements android.view.View.OnClickListener {
        public void onClick(View v) {
            int q = 0;
            greedySolve grdy = new greedySolve();

            while( q <= 0 ){
                grdy.greedSolve(ary);
                grdy.greedyCheck();
                resetArrayAgain( grdy.arry ); // Set new value after route
                RepaintArray();  // puzzle new render display
                try{Thread.sleep(100);}catch(Exception e){}
                count++;
                btnscore.setText(Integer.toString(count));
                eventGame evg =new eventGame();
                if( evg.finalPuzzle(ary) == true ){
         		    //buttonLock();
         			_showAlert("Congratulation  \n You win!",SlideGame.this);
         			
         		}
            	
                q++;
            }
            tex.setText(Integer.toString(grdy.heruetic[0])+" "+Integer.toString(grdy.heruetic[1])+" "+Integer.toString(grdy.heruetic[2])+" "+Integer.toString(grdy.heruetic[3]));
            hue.setText(Integer.toString(grdy.h[0])+" "+Integer.toString(grdy.h[1])+" "+Integer.toString(grdy.h[2])+" "+Integer.toString(grdy.h[3])+" "+Integer.toString(grdy.h[4])+" "+Integer.toString(grdy.h[5])+" "+Integer.toString(grdy.h[6])+" "+Integer.toString(grdy.h[7])+" "+Integer.toString(grdy.h[8])+" "+Integer.toString(grdy.h[9])+" "+Integer.toString(grdy.h[10])+" "+Integer.toString(grdy.h[11])+" "+Integer.toString(grdy.h[12])+" "+Integer.toString(grdy.h[13])+" "+Integer.toString(grdy.h[14])+" "+Integer.toString(grdy.h[15]));
        }
	}*/
    /**
     * Renew array value
    */
    private class astarAi implements android.view.View.OnClickListener {
        public void onClick(View v) {
        	 int q = 0;
             aStarSolve astr = new aStarSolve();
            // while( q <= 20 ){
                
             astr.aStarSolve(ary);
             //astr.setValueAstar(count);
             astr.setContvalue(cnt);
             astr.aStarCheck();
             resetArrayAgain( astr.arry ); // Set new value after route
             RepaintArray();  // puzzle new render display
             try{Thread.sleep(100);}catch(Exception e){}
             cnsl++;             
             count++;
            
             setnewVal( astr.cn );
             btnscore.setText(Integer.toString(count));
            
             eventGame evg =new eventGame();
             counter.cancel();
                if( evg.finalPuzzle(ary) == true ){
         		    buttonLock();
         		   int nu = 90 - Integer.parseInt(btntimes.getText().toString());
         		   _showAlert("Congratulation  \n You win!\n MOVE ="+count+"\n Time ="+Integer.toString(nu)+"\n SOLVE ="+cnsl,SlideGame.this);
         		   cnsl=0;
         			addRow();
         			
         		}
                
                q++;
           // }
           // herues.setText(Integer.toString(astr.heruetic[4])+" "+Integer.toString(astr.heruetic[5])+" "+Integer.toString(astr.heruetic[6])+" "+Integer.toString(astr.heruetic[7]));    
            tex.setText(Integer.toString(astr.heruetic[0])+" "+Integer.toString(astr.heruetic[1])+" "+Integer.toString(astr.heruetic[2])+" "+Integer.toString(astr.heruetic[3]));
            hue.setText(Integer.toString(astr.h[0])+" "+Integer.toString(astr.h[1])+" "+Integer.toString(astr.h[2])+" "+Integer.toString(astr.h[3])+" "+Integer.toString(astr.h[4])+" "+Integer.toString(astr.h[5])+" "+Integer.toString(astr.h[6])+" "+Integer.toString(astr.h[7])+" "+Integer.toString(astr.h[8])+" "+Integer.toString(astr.h[9])+" "+Integer.toString(astr.h[10])+" "+Integer.toString(astr.h[11])+" "+Integer.toString(astr.h[12])+" "+Integer.toString(astr.h[13])+" "+Integer.toString(astr.h[14])+" "+Integer.toString(astr.h[15]));
        }
        
	} private void setnewVal( int cm[] ){
    	for(int i=0;i<=15;i++){
    		cnt[i] = cm[i];
    	}
    }
    /**
     * Renew array value
    */
    private void resetArrayAgain( String aryNew[][]){
         for(int i = 0; i <= 3; i++){
    		for(int j = 0; j <= 3; j++){
    			ary[i][j] = aryNew[i][j];
    		}
    	}
    }
    protected void RepaintArray(){
        btn0.setText(ary[0][0]);        btn1.setText(ary[0][1]);
        btn2.setText(ary[0][2]);        btn3.setText(ary[0][3]);
        btn4.setText(ary[1][0]);        btn5.setText(ary[1][1]);
        btn6.setText(ary[1][2]);        btn7.setText(ary[1][3]);
        btn8.setText(ary[2][0]);        btn9.setText(ary[2][1]);
        btn10.setText(ary[2][2]);       btn11.setText(ary[2][3]);
        btn12.setText(ary[3][0]);       btn13.setText(ary[3][1]);
        btn14.setText(ary[3][2]);       btn15.setText(ary[3][3]);
    }
    private void getButtonId(){
    	btn0  = (Button) this.findViewById(R.id.Button00);
        btn1  = (Button) this.findViewById(R.id.Button01);
        btn2  = (Button) this.findViewById(R.id.Button02);
        btn3  = (Button) this.findViewById(R.id.Button03);
        btn4  = (Button) this.findViewById(R.id.Button10);
        btn5  = (Button) this.findViewById(R.id.Button11);
        btn6  = (Button) this.findViewById(R.id.Button12);
        btn7  = (Button) this.findViewById(R.id.Button13);
        btn8  = (Button) this.findViewById(R.id.Button20);
        btn9  = (Button) this.findViewById(R.id.Button21);
        btn10 = (Button) this.findViewById(R.id.Button22);
        btn11 = (Button) this.findViewById(R.id.Button23);
        btn12 = (Button) this.findViewById(R.id.Button30);
        btn13 = (Button) this.findViewById(R.id.Button31);
        btn14 = (Button) this.findViewById(R.id.Button32);
        btn15 = (Button) this.findViewById(R.id.Button33);
        btnNew = (Button) this.findViewById(R.id.btnNew);
        btnscore = (Button) this.findViewById(R.id.btnScore);
        //btnGreedy = (Button) this.findViewById(R.id.btnGreedy);
        btnAstar =(Button) this.findViewById(R.id.btnAstar);
        tex = (TextView) this.findViewById(R.id.TextView01);
        hue = (TextView) this.findViewById(R.id.Tex2);
        btntimes = (Button) this.findViewById(R.id.btntimes);
        btnHgtScore  = (Button) this.findViewById(R.id.btnHgtScore);
        
       // user =  (EditText) this.findViewById(R.id.user);
       // herues = (TextView) this.findViewById(R.id.herue);
        //help = (Button) this.findViewById(R.id.Help);
       // back = (Button) this.findViewById(R.id.back);
    }
    private boolean CheckEmptyBox(int x , int y){
    	//CheckTOP
    	if((x-1)>=0){
    		if(ary[(x-1)][y] == " "){
    			String buffer = ary[x-1][y];
    			ary[x-1][y] = ary[x][y];
    			ary[x][y] = buffer;
    			return true;
    		}
    	}
    	//checkButtom
    	if((x+1)<=3){
    		if(ary[(x+1)][y] == " "){
    			String buffer = ary[x+1][y];
    			ary[x+1][y] = ary[x][y];
    			ary[x][y] = buffer;
    			return true;
    		}
    	}
    	//CheckLeft
    	if((y-1)>=0){
    		if(ary[(x)][y-1] == " "){
    			String buffer = ary[x][y-1];
    			ary[x][y-1] = ary[x][y];
    			ary[x][y] = buffer;
    			return true;
    		}
    	}
    	//checkRight
    	if((y+1)<=3){
    		if(ary[(x)][y+1] == " "){
    			String buffer = ary[x][y+1];
    			ary[x][y+1] = ary[x][y];
    			ary[x][y] = buffer;
    			return true;
    		}
    	}
    	return false;
    }
    private CharSequence findinArray(CharSequence current ){
    	for(int i=0;i<= 3;i++)
    		for(int j=0;j<= 3;j++) {
    			if(ary[i][j] == current) {
    				return String.valueOf(i)+","+String.valueOf(j);
    			}
    		}
    	return "0,0";
    }
    /**
     *  Method initial slide puzzle number.
     */
    private void initPuzzle(){
    	count = 0;
    	btnscore.setText(Integer.toString(count));
    	//String []startArr = new String[]{ "1", "2", "3", "4", "5", "6", "7","8","9","10","11","12","13","14","15"," " };
    	shuffleArray();
    	//newArry(startArr);
    }
    /**
     *  Method shuffle array.
     * @param a
     */
    private void swaparray( int a, int b ,int c , int d ){
        String tmp   = ary[a][b];
        ary[a][b] = ary[c][d];
        ary[c][d] = tmp;
	}
    public void shuffleArray(){
		int xx = 3;
		int yy = 3;
		
		ary[0][0] ="1";ary[1][1] ="6";ary[2][2] ="11";ary[3][3] =" ";
		ary[0][1] ="2";ary[1][2] ="7";ary[2][3] ="12";
		ary[0][2] ="3";ary[1][3] ="8";ary[3][0] ="13";
		ary[0][3] ="4";ary[2][0] ="9";ary[3][1] ="14";
		ary[1][0] ="5";ary[2][1] ="10";ary[3][2] ="15";
	
		Random random = new Random();
		for(int loop = 0;loop<=100;loop++)
		{
			int i ;
			do
			{
				i = random.nextInt();
				i = Math.abs(i);
				
				i = i%5;
			}while(!((i < 5)&&(i>0)));
			//tex.setText(Integer.toString(i));
			
			if(i == 1)
			{
				if((xx-1)>=0)//check top
				{
				 swaparray(xx,yy,xx-1,yy);
				 xx = xx-1;
				}else
				{
				 continue;
				}
				
			}
			else if(i == 2)
			{
				if((yy-1)>=0)//check left
				{
				 swaparray(xx,yy,xx,yy-1);
				 yy = yy-1;
				}else
				{
				 continue;
				}
			
			}
			else if(i == 3)
			{
				if((xx+1)<=3)//check buttom
				{
				 swaparray(xx,yy,xx+1,yy);
				 xx = xx+1;
				}else
				{
				 continue;
				}
			}
			else if(i == 4)
			{
				if((yy+1)<=3)//check right
				{
				 swaparray(xx,yy,xx,yy+1);
				 yy = yy+1;
				}else
				{
				 continue;
				}
			}
		}
		
	}
    public void newArry(String[] arry){
    	int j = 0, k = 0;
    	for(int i = 0; i < 16; i++){
    		ary[j][k] = arry[i];
    		k++;
    		if( (k % 4) == 0){
    			k = 0;
    			j++;
    		}
    	}
    }
    /**
     * Method swap array.
     * @param a
     * @param i
     * @param change
     */
	/*private static void swap(String[] a, int i, int change){
		String origin = a[i];
		a[i] = a[change];
		a[change] = origin;
	}*/
	private void buttonLock(){
    	btn0.setEnabled(false);     	btn1.setEnabled(false);
    	btn2.setEnabled(false);    	btn3.setEnabled(false);
    	btn4.setEnabled(false);    	btn5.setEnabled(false);
    	btn6.setEnabled(false);    	btn7.setEnabled(false);
    	btn8.setEnabled(false);    	btn9.setEnabled(false);
    	btn10.setEnabled(false);    btn11.setEnabled(false);
    	btn12.setEnabled(false);    btn13.setEnabled(false);
    	btn14.setEnabled(false);    btn15.setEnabled(false);
    	//btnGreedy.setEnabled(false);  
        btnAstar.setEnabled(false); 
    }
    private void buttonUnLock(){
    	btn0.setEnabled(true);      btn1.setEnabled(true);
 
    	btn2.setEnabled(true);    	btn3.setEnabled(true);
    	btn4.setEnabled(true);    	btn5.setEnabled(true);
    	btn6.setEnabled(true);    	btn7.setEnabled(true);
    	btn8.setEnabled(true);    	btn9.setEnabled(true);
    	btn10.setEnabled(true);    	btn11.setEnabled(true);
    	btn12.setEnabled(true);    	btn13.setEnabled(true);
    	btn14.setEnabled(true);    	btn15.setEnabled(true);
    	//user.setEnabled(false);
    	//btnGreedy.setEnabled(true);  
        btnAstar.setEnabled(true);
    }
    /**
     * Method close program
     */
    /*private void onClose(){
    	System.exit(0);
    }*/
    
    /**
     * Show message by alert
     * @param message
     * @param c current context
     */
    private void _showAlert(final String message, final Context c) {
    	Builder builder = new AlertDialog.Builder(c);
    	builder.setMessage(message);
    	builder.setPositiveButton(android.R.string.ok,
    		new DialogInterface.OnClickListener() {
    			public void onClick(DialogInterface dialog, int which) {
    					// do nothing
    				}
    			});
    	AlertDialog dialog = builder.create();
    	dialog.show();
    }


    /**
     * Show context on UiThread
     * @param message
     * @param current context
     */
    /*private void showToast(final String msg, final Context c) {
    	Runnable showToastTask = new Runnable() {
    		public void run() {
    			Toast.makeText(c, msg, Toast.LENGTH_SHORT).show();
    		}
    	};
    	runOnUiThread(showToastTask);
    }*/
    private void resetValue(){
    	cnt[0] = 0;
    	cnt[1] = 0;
    	cnt[2] = 0;
    	cnt[3] = 0;
    	cnt[4] = 0;
    	cnt[5] = 0;
    	cnt[6] = 0;
    	cnt[7] = 0;
    	cnt[8] = 0;
    	cnt[9] = 0;
    	cnt[10] = 0;
    	cnt[11] = 0;
    	cnt[12] = 0;
    	cnt[13] = 0;
    	cnt[14] = 0;
    	cnt[15] = 0;
    }
    class MyCount extends CountDownTimer{

    	public MyCount(long millisInFuture, long countDownInterval) {
    		super(millisInFuture, countDownInterval);
    		// TODO Auto-generated constructor stub
    		
    	}

    	@Override
    	public void onFinish() {
    		// TODO Auto-generated method stub
    		//btntimes.setText("done");
    		btntimes.setText("0");
    		buttonLock();
    		_showAlert("Timeout  \n You lose!",SlideGame.this);
    		
    	}

    	@Override
    	public void onTick(long millisUntilFinished) {
    		// TODO Auto-generated method stub
    		
    		btntimes.setText(""+millisUntilFinished/1000);
    		
    		
    	}
    	
      }
    private void addRow(){
 
    	try
    	{
    		int nu = 90 - Integer.parseInt(btntimes.getText().toString());
    		int nus = 1 + Integer.parseInt(btnscore.getText().toString());
    		db.addRow(Integer.toString(nu),Integer.toString(nus));
 
	    	//updateTable();
 
    		//emptyFormFields();
    	}
    	catch (Exception e)
    	{
    		_showAlert(btntimes.getText().toString() ,SlideGame.this);
    		_showAlert(btnscore.getText().toString() ,SlideGame.this);
    	}
    }

    
}

 